#ifndef TEXTURECUH
#define TEXTURECUH
#include"raytracingtool.cuh"
#include"perlin.cuh"
class texture
{
public:
    __device__ virtual vec3 value(double u, double v, const vec3& p) const = 0;
    __duel__ virtual ~texture(){};
};
class constant_texture : public texture {
    public:
        __duel__ constant_texture() {}
        __duel__ constant_texture(vec3 c) : color(c) {}

        __device__ virtual vec3 value(double u, double v, const vec3& p) const {
            return color;
        }
    __duel__ virtual ~constant_texture(){};
    public:
        vec3 color;
};
class checker_texture : public texture {
public:
    __duel__ checker_texture() {}
    __duel__ checker_texture(texture* t0, texture* t1): even(t0), odd(t1) {}

    __device__ virtual vec3 value(double u, double v, const vec3& p) const {
        auto sines = sin(10*p.x())*sin(10*p.y())*sin(10*p.z());
        if (sines < 0)
            return odd->value(u, v, p);
        else
            return even->value(u, v, p);
            
    }
    __duel__ virtual ~checker_texture(){THISNULL(odd);THISNULL(even);};
public:
    texture* odd;
    texture* even;
};
class noise_texture : public texture {
public:
    __duel__ noise_texture(curandState *local_rand_state)
    :scale(0),noise(local_rand_state) 
    {}
    __duel__ noise_texture(float sc,curandState *local_rand_state) 
    : scale(sc),noise(local_rand_state) {}

    __device__ virtual vec3 value(float u, float v, const vec3& p) const {
            return vec3(1,1,1) * 0.5 * (1.0 + noise.noise(scale * p));
    }

public:
    perlin noise;
    float scale;
};














#endif